﻿using System;
using System.Collections.Generic;
using System.Linq;
using Spanner;

namespace SpannerWebSite
{
    internal partial class LoginDemo : UI
    {
        enum Mode { LogIn, SignUp };

        internal static Html Content()
        {
            var mode = ObsVar("mode", Mode.LogIn);

            var name = ObsVar("name", "");

            var password = ObsVar("password", "");

            var email = ObsVar("email", "");

            var errMsg = ObsVar("errMsg", "");

            var busy = ObsVar("busy", false);

            var validEmailRE = Var("validEmailRE", NewRegExp(@"\\w\\w\\w@\\w\\w\\w"));

            var fakeRPC = Procedure("fakeRPC", Do(
                Set(busy, false),
                Alert("Welcome!") // Everyone's a winner.
            ));

            var go = Procedure("go",
                IfCase(
                    When(name == "",
                        Set(errMsg, "Please provide a log-in name.")
                    ),
                    When(password == "",
                        Set(errMsg, "Please provide a valid password.")
                    ),
                    When(mode == Mode.SignUp & !Test(validEmailRE, email),
                        Set(errMsg, "Please provide a valid e-mail address.")
                    ),
                    Otherwise(Do(
                        Set(busy, true),
                        Do(SetTimeout(fakeRPC, 1000)) // Pretend we're talking to a remote service.
                    ))
                )
            );

            var chgMode = Procedure<Mode>("chgMode", x => Do(
                Set(mode, x),
                Set(errMsg, "")
            ));

            var content = Div().WithClass("login-demo").WithChildren(
                Div().WithAttr("style",
                        "border: 4px solid black; margin: 1em; padding: 1em; width: 16em").WithChildren(
                    B("Log-in/Sign-up Demo"),
                    Div().KoIf(mode == Mode.LogIn).WithChildren(
                        H3("Log in or ", Button("sign up").KoClick(Call(chgMode, Mode.SignUp)))
                    ),
                    Div().KoIf(mode == Mode.SignUp).WithChildren(
                        H3("Sign up or ", Button("log in").KoClick(Call(chgMode, Mode.LogIn)))
                    ),
                    Table(
                        TR(TD("Name"),      TD(Input().KoValue(name))),
                        TR(TD("Password"),  TD(Input().KoValue(password).WithAttr("type", "password"))),
                        TR(TD("E-mail"),    TD(Input().KoValue(email))).KoVisible(mode == Mode.SignUp),
                        TR(TD(""),          TD(Show(errMsg).WithClass("login-demo-error").KoVisible(errMsg != "")))
                    ),
                    Button("Go!").KoClick(go).KoEnabled(!busy),
                    Span("processing...").KoIf(busy)
                )
            );

            return content;
        }

        internal static void WriteWebPage()
        {
            const string path = Const.DemoWebSitePath;
            var content = Content();
            var html = StandardSpannerHtmlPage("Login demo", content);
            var webPage = WebPage("LoginDemo", html, null);
            var ctxt = new Context(path);
            ctxt.WriteWebPage(webPage);
        }
    }
}
